package cn.com.oceansoft.osc.ms.controller;

import cn.com.oceansoft.osc.ms.config.AppConstant;
import cn.com.oceansoft.osc.ms.domain.ZxxxConfig;
import cn.com.oceansoft.osc.ms.domain.ZxxxInfo;
import cn.com.oceansoft.osc.ms.service.IZxxxService;
import cn.com.oceansoft.osc.ms.utils.HttpClientUtil;
import cn.com.oceansoft.osc.ms.utils.signaclass;
import cn.ucox.web.framework.cache.RedisClient;
import cn.ucox.web.framework.exception.CacheOperationException;
import cn.ucox.web.framework.view.ApiResult;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.validation.Valid;
import java.io.UnsupportedEncodingException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.*;

import static org.springframework.web.bind.annotation.RequestMethod.GET;
import static org.springframework.web.bind.annotation.RequestMethod.POST;

@RestController
@RequestMapping(value = "ZXXX")
public class ZXXXController {
    private static final Logger logger = LoggerFactory.getLogger(ZXXXController.class);
    @Resource
    private IZxxxService zxxxService;
    @Resource
    private RedisClient redisClient;

    /**
     * 此方法放最后，防止路径冲突
     *
     * @param
     * @param
     * @return
     */
    @GetMapping("version")
    @ApiOperation("获取服务版本号")
    @ApiImplicitParam(paramType = "path", name = "id", dataType = "String", required = true, value = "办件编号")
    public ApiResult showVersion() {

        String version = "0.01";
        return new ApiResult<Object>().success(version);
    }

    @RequestMapping(value = "selectZInfo", method = GET)
    @ApiOperation("通过装修信息")
    public ApiResult selectZInfo() throws Exception {
        List<ZxxxInfo> list = zxxxService.selectZInfo();
        if (list.size() > 0) {
            return new ApiResult<List<ZxxxInfo>>().success(AppConstant.SUCCES_ZXXX, "", list);
        } else {
            return new ApiResult<List<ZxxxInfo>>().failure(-1, "", list);
        }
    }

    @RequestMapping(value = "selectZInfotemp/{guid}", method = GET)
    @ApiOperation("通过装修信息")
    public ApiResult selectZInfotemp(@PathVariable(value = "guid") String guid) throws Exception {
        List<ZxxxInfo> list = zxxxService.selectZInfotemp(guid);
        if (list.size() > 0) {
            return new ApiResult<List<ZxxxInfo>>().success(AppConstant.SUCCES_ZXXX, "", list);
        } else {
            return new ApiResult<List<ZxxxInfo>>().failure(-1, "", list);
        }
    }

    @RequestMapping(value = "selectZInfowst", method = GET)
    @ApiOperation("通过装修信息")
    public ApiResult selectZInfowst(String wst) throws Exception {
        wst = "%" + wst + "%";
        List<ZxxxInfo> list = zxxxService.selectZInfowst(wst);
        if (list.size() > 0) {
            return new ApiResult<List<ZxxxInfo>>().success(AppConstant.SUCCES_ZXXX, "", list);
        } else {
            return new ApiResult<List<ZxxxInfo>>().failure(-1, "", list);
        }
    }

    @RequestMapping(value = "selectZInfowsttemp/{guid}", method = GET)
    @ApiOperation("通过装修信息--个人接口")
    public ApiResult selectZInfowsttemp(@PathVariable(value = "guid") String guid, String wst) throws Exception {
        wst = "%" + wst + "%";
        List<ZxxxInfo> list = zxxxService.selectZInfowsttemp(wst, guid);
        if (list.size() > 0) {
            return new ApiResult<List<ZxxxInfo>>().success(AppConstant.SUCCES_ZXXX, "", list);
        } else {
            return new ApiResult<List<ZxxxInfo>>().failure(-1, "", list);
        }
    }

    @RequestMapping(value = "selectZInfoguid/{guid}", method = GET)
    @ApiOperation("通过GUID查询装修信息")
    public ApiResult selectZInfo(@PathVariable(value = "guid") String guid) throws Exception {
        ZxxxInfo list = zxxxService.selectZInfoguid(guid);
        if (list != null) {
            return new ApiResult<ZxxxInfo>().success(AppConstant.SUCCES_ZXXX, "", list);
        } else {
            return new ApiResult<ZxxxInfo>().failure(-1, "", list);
        }
    }

    @PostMapping("insertZInfo")
    @ApiOperation("新增装修信息")
    @ApiImplicitParam(paramType = "body", name = "ZxxxInfo", dataType = "ZxxxInfo", required = true, value = "装修信息")
    public ApiResult insertZInfo(@RequestBody @Valid ZxxxInfo zxxxInfo) throws Exception {
        int i = zxxxService.insertZInfo(zxxxInfo);
        if (i > 0) {
            return new ApiResult<Object>().success("保存成功");
        } else {
            return new ApiResult<Object>().failure("保存失败");
        }
    }

    @PostMapping("updateZInfo")
    @ApiOperation("修改装修信息")
    @ApiImplicitParam(paramType = "body", name = "ZxxxInfo", dataType = "ZxxxInfo", required = true, value = "装修信息")
    public ApiResult updateZInfo(@RequestBody ZxxxInfo zxxxInfo) throws Exception {
        int i = zxxxService.updateZInfo(zxxxInfo);
        if (i > 0) {
            return new ApiResult<Object>().success("保存成功");
        } else {
            return new ApiResult<Object>().failure("保存失败");
        }
    }

    @GetMapping(value = "deleteZInfo/{guid}")
    @ApiOperation("删除装修信息")
    public ApiResult deleteZInfo(@PathVariable(value = "guid") String guid) throws Exception {
        int i = zxxxService.deleteZInfo(guid);
        if (i > 0) {
            return new ApiResult<Object>().success("删除成功");
        } else {
            return new ApiResult<Object>().failure("删除失败");
        }
    }

    @PostMapping("selectZConfig")
    @ApiOperation("获取配置信息")
    public ApiResult selectZConfig(@RequestBody Map<String, String> map) throws Exception {
        String type = "";
        String infoguid = "";
        if (map.containsKey("type")) {
            type = map.get("type");
        }
        if (map.containsKey("infoguid")) {
            infoguid = map.get("infoguid");
        }
        ZxxxConfig list = zxxxService.selectZConfig(type, infoguid);
        if (list != null) {
            return new ApiResult<ZxxxConfig>().success(AppConstant.SUCCES_ZXXX, "", list);
        } else {
            return new ApiResult<ZxxxConfig>().failure(-1, "", list);
        }
    }

    @PostMapping("insertZConfig")
    @ApiOperation("新增配置信息")
    @ApiImplicitParam(paramType = "body", name = "ZxxxConfig", dataType = "ZxxxConfig", required = true, value = "配置信息")
    public ApiResult insertZConfig(@RequestBody ZxxxConfig zxxxConfig) throws Exception {
        int i = zxxxService.insertZConfig(zxxxConfig);
        if (i > 0) {
            return new ApiResult<Object>().success("保存成功");
        } else {
            return new ApiResult<Object>().failure("保存失败");
        }
    }

    @PostMapping("updateZConfig")
    @ApiOperation("修改装修信息")
    @ApiImplicitParam(paramType = "body", name = "ZxxxConfig", dataType = "ZxxxConfig", required = true, value = "配置信息")
    public ApiResult updateZConfig(@RequestBody ZxxxConfig zxxxConfig) throws Exception {
        int i = zxxxService.updateZConfig(zxxxConfig);
        if (i > 0) {
            return new ApiResult<Object>().success("保存成功");
        } else {
            return new ApiResult<Object>().failure("保存失败");
        }
    }

    @GetMapping("deleteZConfig/{guid}")
    @ApiOperation("删除配置信息")
    public ApiResult deleteZConfig(@PathVariable(value = "guid") String guid) throws Exception {
        int i = zxxxService.deleteZConfig(guid);
        if (i > 0) {
            return new ApiResult<Object>().success("删除成功");
        } else {
            return new ApiResult<Object>().failure("删除失败");
        }
    }

    @GetMapping("deleteZConfiginfo/{guid}")
    @ApiOperation("删除配置信息")
    public ApiResult deleteZConfiginfo(@PathVariable(value = "guid") String guid) throws Exception {
        int i = zxxxService.deleteZConfiginfo(guid);
        if (i > 0) {
            return new ApiResult<Object>().success("删除成功");
        } else {
            return new ApiResult<Object>().failure("删除失败");
        }
    }


    //----------------------------------------微信接口服务【start】-------------------------------------
    @GetMapping("gettoken")
    @ApiOperation("获取token")
    public ApiResult gettoken() throws IllegalArgumentException, CacheOperationException {
        if (!redisClient.hasKey("tokeninfo")) {
            String url = AppConstant.WX_TOKEN_URL + "?grant_type=client_credential&appid=" + AppConstant.WX_APPID + "&secret=" + AppConstant.WX_SECRET;
            ApiResult apiResult = new ApiResult();
            try {
                String Result = HttpClientUtil.doGet(url);
                apiResult.setCode(200);
                apiResult.setSucc(true);
                apiResult.setData(Result);
                redisClient.save("tokeninfo", Result, 7200);
            } catch (Exception ex) {
                apiResult.setCode(-1);
                apiResult.setSucc(false);
                apiResult.setData(ex.getMessage());
            }
            return apiResult;
        } else {
            String Result = redisClient.get("tokeninfo").toString();
            ApiResult apiResult = new ApiResult();
            apiResult.setCode(200);
            apiResult.setSucc(true);
            apiResult.setData(Result);
            return apiResult;
        }
    }

    @RequestMapping(value = "getticket/{token}", method = GET)
    @ApiOperation("获取getticket")
    @ApiImplicitParam(paramType = "path", name = "token", dataType = "String", required = true, value = "token唯一标识")
    public ApiResult getticket(@PathVariable(value = "token") String token) throws IllegalArgumentException, CacheOperationException {
        if (!token.isEmpty()) {
            if (!redisClient.hasKey("ticketinfo")) {
                String url = AppConstant.WX_TICKET_URL + "?access_token=" + token + "&type=jsapi";
                ApiResult apiResult = new ApiResult();
                try {
                    String Result = HttpClientUtil.doGet(url);
                    apiResult.setCode(200);
                    apiResult.setSucc(true);
                    apiResult.setData(Result);
                    redisClient.save("ticketinfo", Result, 7200);
                } catch (Exception ex) {
                    apiResult.setCode(-1);
                    apiResult.setSucc(false);
                    apiResult.setData(ex.getMessage());
                }
                return apiResult;
            } else {
                String Result = redisClient.get("ticketinfo").toString();
                ApiResult apiResult = new ApiResult();
                apiResult.setCode(200);
                apiResult.setSucc(true);
                apiResult.setData(Result);
                return apiResult;
            }
        } else {
            ApiResult apiResult = new ApiResult();
            apiResult.setCode(-1);
            apiResult.setSucc(false);
            apiResult.setData("token值必传");
            return apiResult;
        }
    }


    @RequestMapping(value = "signature", method = RequestMethod.POST)
    @ApiOperation("获取签名")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "body", name = "signa", dataType = "signaclass", required = true, value = "签名参数")
    })
    public Map<String, String> signature(@RequestBody signaclass signa) throws Exception {
        Map<String, String> sha1str = new HashMap<String, String>();
        try {
            String jsapi_ticket = signa.getJsapi_ticket();
            String url = signa.getUrl();
            sha1str = sign(jsapi_ticket, url);
            return sha1str;
        } catch (Exception ex) {
            logger.error("获取签名出错：原因" + ex.getMessage());
            return sha1str;
        }
    }

    public Map<String, String> sign(String jsapi_ticket, String url) {
        Map<String, String> ret = new HashMap<String, String>();
        String nonce_str = create_nonce_str();
        String timestamp = create_timestamp();
        String string1;
        String signature = "";

        //注意这里参数名必须全部小写，且必须有序
        string1 = "jsapi_ticket=" + jsapi_ticket +
                "&noncestr=" + nonce_str +
                "&timestamp=" + timestamp +
                "&url=" + url;
        System.out.println(string1);

        try {
            MessageDigest crypt = MessageDigest.getInstance("SHA-1");
            crypt.reset();
            crypt.update(string1.getBytes("UTF-8"));
            signature = byteToHex(crypt.digest());
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }
        ret.put("url", url);
        ret.put("jsapi_ticket", jsapi_ticket);
        ret.put("nonceStr", nonce_str);
        ret.put("timestamp", timestamp);
        ret.put("signature", signature);
        return ret;
    }

    private String byteToHex(final byte[] hash) {
        Formatter formatter = new Formatter();
        for (byte b : hash) {
            formatter.format("%02x", b);
        }
        String result = formatter.toString();
        formatter.close();
        return result;
    }

    private String create_nonce_str() {
        return UUID.randomUUID().toString();
    }

    private String create_timestamp() {
        return Long.toString(System.currentTimeMillis() / 1000);
    }
    //----------------------------------------微信接口服务【end】-------------------------------------
}
